<template>
  <el-form-item
    label="商品规格"
    prop="products"
    :rules="rules"
  >
    <el-row class="form-inline-row">
      <el-form-item>
        <el-select
          placeholder="请选择规格"
          clearable
          @change="selectProduct"
        >
          <el-option
            v-for="(item) in productOptions"
            :key="item.id"
            :label="item.name"
            :value="item.id"
          />
        </el-select>
      </el-form-item>
    </el-row>
  </el-form-item>

  <el-form-item>
    <el-table :data="selectedProducts">
      <slot name="product-column" />
      <el-table-column
        label="操作"
        fixed="right"
      >
        <template #default="scope">
          <el-button
            link
            type="primary"
            @click="deleteProduct(scope.row, scope.$index)"
          >
            删除
          </el-button>
        </template>
      </el-table-column>
    </el-table>
  </el-form-item>
</template>

<script lang="ts" setup>
import {IStoreProductRow} from "@/api/modules/pointsMall";

const props = withDefaults(defineProps<{
  modelValue: IStoreProductRow[]
  productOptions: IStoreProductRow[]
  columnProps: string[]
}>(), {
  modelValue: [] as any,
  productOptions: [] as any,
  columnProps: [] as any
})
const emits = defineEmits(['update:model-value'])

// 初始化
const productOptionsRef = toRef(props, 'productOptions')
const productOptions = ref<IStoreProductRow[]>([])
watch(productOptionsRef, (newValue) => {
  productOptions.value = newValue.map(item => ({
    ...item,
    thumbnailUrl: item.thumbnailUrl ?? '', // upload组件需要
    payOfCurrencyCount: 0,
  }))
})

// 已选中的规格
const selectedProducts = ref<IStoreProductRow[]>([])

// 选中规格
const selectProduct = (val: string) => {
  const target = productOptions.value.find(item => item.id === val)
  if (target) {
    selectedProducts.value.push({
      ...target,
      storeProductId: target.id
    })
  }
}

// 更新form数据
watch(selectedProducts, (newValue) => {
  emits("update:model-value", newValue)
}, {
  deep: true
})

// 删除规格
const deleteProduct = (row: IStoreProductRow, index: number) => {
  selectedProducts.value.splice(index, 1)
}

const isEmpty = (val: any) => {
  return val === null || val === undefined || val === ''
}

const rules = [
  {
    required: true,
    validator(rule, val, callback) {
      if (!selectedProducts.value.length) {
        callback(new Error('请添加商品规格'))
      } else {
        callback()
      }
    }
  },
  {
    validator(rule:any, val:any, callback: any) {
      for (let i = 0; i < selectedProducts.value.length; i++) {
        const row = selectedProducts.value[i]

        if (props.columnProps.includes('name')) {
          if (isEmpty(row.name)) {
            callback(`请输入规格表第${i + 1}行的规格名称`)
            return
          }
        }

        if (props.columnProps.includes('thumbnailUrl')) {
          if (isEmpty(row.thumbnailUrl)) {
            callback(`请上传规格表第${i + 1}行的规格图片`)
            return
          }
        }

        if (props.columnProps.includes('salePrice')) {
          if (!/^(0|[1-9][0-9]*)$/.test('' + row.payOfCurrencyCount)) {
            callback(`请输入规格表第${i + 1}行的售价（积分），且只能为0或正整数`)
            return
          }

          if (Number(row.payOfCurrencyCount) > 9999999999) {
            callback(`规格表第${i + 1}行的售价（积分），超过上限【99,9999,9999】`)
            return
          }

          if (!/(^[0-9]+$)|(^[0-9]+\.[0-9]{1,2}$)/.test('' + row.payPrice)) {
            callback(`规格表第${i + 1}行的售价（现金）不正确，不能为负数且仅保留2位小数`)
            return
          }

          if (Number(row.payPrice) > 9999999999) {
            callback(`规格表第${i + 1}行的售价（现金），超过上限【99,9999,9999】`)
            return
          }
        }

        if (props.columnProps.includes("payOfCurrencyId")) {
          if (!row.payOfCurrencyId) {
            callback(`规格表第${i + 1}行的积分类型未选择`)
            return
          }
        }

        if (props.columnProps.includes('addOrDeductionStockCount')) {
          if (isEmpty(row.addOrDeductionStockCount)) {
            callback(`规格表第${i + 1}行的库存增减量不能为空`)
            return
          }

          if (row.addOrDeductionStockCount > row.beforeStock) {
            callback(`规格表第${i + 1}行的库存增减量不能大于预占库存`)
            return
          }

          if (row.addOrDeductionStockCount < 1) {
            callback(`规格表第${i + 1}行的库存增减量不能小于1`)
            return
          }
        }
      }

      callback()
    }
  }
]

</script>

<style scoped lang="scss">
.form-inline-row {
  //margin-bottom: 5px;
}
</style>
